//
// Copyright (C) 2008 Jackson Harper (jackson@ximian.com)

// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
// as published by the Free Software Foundation; either version 2
// of the License, or (at your option) any later version.

// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.

// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
//
//

using System;
using System.Data;
using System.Web;
using System.Web.Security;
using System.Configuration;
using System.Collections.Generic;

using log4net;
using MySql.Data.MySqlClient;

namespace Grr.Models
{
	public class Revision
	{
		private static readonly ILog log = LogManager.GetLogger(typeof(Revision));

		private string grurrah;
		private long grurrah_id;

		private long id;
		private string text;
		private string created_by;
		private string creator_ip;

		public Revision(long id, string text, long grurrah_id, string grurrah, string created_by, string creator_ip)
		{
			this.id = id;
			this.text = text;
			this.grurrah_id = grurrah_id;
			this.grurrah = grurrah;
			this.created_by = created_by;
			this.creator_ip = creator_ip;
		}

		public long Id
		{
			get { return id; }
		}

		public string GrurrahName
		{
			get { return grurrah; }
		}

		public long GrurrahId
		{
			get { return grurrah_id; }
		}

		public string Text
		{
			get { return text; }
		}

		public string CreatedBy
		{
			get { return created_by; }
		}

		public string CreatorIp
		{
			get { return creator_ip; }
		}

		private static int IdColumn = 0;
		private static int TextColumn = 1;
		private static int GrurrahIdColumn = 2;
		private static int GrurrahNameColumn = 3;
		private static int CreatorIdColumn = 4;
		private static int CreatorIpColumn = 5;

		private static string SelectUnmoderated = "SELECT Revisions.id, Revisions.text, Revisions.grurrah_id, Grurrahs.name, Revisions.creator_id, Revisions.creator_ip FROM Revisions JOIN Grurrahs ON Revisions.grurrah_id = Grurrahs.id WHERE Revisions.is_approved = 0";

		public static List<Revision> GetUnmoderatedRevisions()
		{
			List<Revision> revisions = new List<Revision>();

			using (MySqlConnection rcon = DbContext.OpenReadConnection())
			{
				MySqlCommand cmd = new MySqlCommand(SelectUnmoderated, rcon);
				MySqlDataReader reader = cmd.ExecuteReader();

				while (reader.Read())
				{
					long id = reader.GetInt64(IdColumn);
					string text = reader.GetString(TextColumn);
					long grurrah_id = reader.GetInt64(GrurrahIdColumn);
					string grurrah_name = reader.GetString(GrurrahNameColumn);
					long creator_id = reader.GetInt64(CreatorIdColumn);
					string creator_ip = reader.GetString(CreatorIpColumn);
					string created_by = "Anonymous";

					MembershipUser creator = Membership.GetUser(creator_id);
					if (creator != null)
						created_by = creator.UserName;

					Revision rev = new Revision(id, text, grurrah_id, grurrah_name, created_by, creator_ip);
					revisions.Add(rev);
				}
			}

			return revisions;
		}


		public static void Approve(long revision_id)
		{
			using (MySqlConnection rwcon = DbContext.OpenReadWriteConnection())
			{
				MySqlCommand cmd = new MySqlCommand("UPDATE Revisions SET is_approved = 1 WHERE id = ?revision_id", rwcon);
				cmd.Parameters.Add("?revision_id", MySqlDbType.Int64).Value = revision_id;

				if (cmd.ExecuteNonQuery() != 1)
				{
					log.ErrorFormat("Unable to set is_approved on Revisions for revision: {0}", revision_id);
					return;
				}
			}
		}

		public static void Delete (long revision_id, long grurrah_id)
		{
			using (MySqlConnection rwcon = DbContext.OpenReadWriteConnection())
			{
				MySqlCommand cmd = new MySqlCommand("SELECT id FROM Revisions WHERE grurrah_id = ?grurrah_id AND id != ?revision_id ORDER BY created_time DESC LIMIT 0,1", rwcon);
				cmd.Parameters.Add("?grurrah_id", MySqlDbType.Int64).Value = grurrah_id;
				cmd.Parameters.Add("?revision_id", MySqlDbType.Int64).Value = revision_id;

				object new_revision_id = cmd.ExecuteScalar();

				if (new_revision_id == null)
				{
					Grurrah.Delete(grurrah_id);
					return;
				}

				cmd = new MySqlCommand("UPDATE Grurrahs SET revision_id = ?new_revision_id WHERE id = ?grurrah_id", rwcon);
				cmd.Parameters.Add("?grurrah_id", MySqlDbType.Int64).Value = grurrah_id;
				cmd.Parameters.Add("?new_revision_id", MySqlDbType.Int64).Value = new_revision_id;

				if (cmd.ExecuteNonQuery() != 1)
				{
					log.ErrorFormat("Unable to set new Revision ID for Grurrah with a deleted revision:  grurrah_id: {0}  old revision: {1}  new revision:	{2}", grurrah_id, revision_id, new_revision_id);
					return;
				}

				cmd = new MySqlCommand("DELETE FROM Revisions WHERE id = ?revision_id", rwcon);
				cmd.Parameters.Add("?revision_id", MySqlDbType.Int64).Value = revision_id;

				if (cmd.ExecuteNonQuery() != -1)
				{
					log.ErrorFormat("Unable to DELETE Revision FROM Revisions:	revision_id: {0} grurrah_id: {1}", revision_id, grurrah_id);
					return;
				}
			}
		}

	}
}